﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using NUnit.Framework;
using FileModelNS;

namespace FileModelTest
{
	[TestFixture]
	public class FileFormatTest
	{
		[Test]
		public void testLoading()
		{
			var fileContents = new FileContents(@"..\..\TestResource\notepad.exe");
			var fileFormat = new FileFormat(@"..\..\TestResource\Windows PE Format.xml", fileContents);

			var tree = fileFormat.Tree;

			// 1 root node
			Assert.AreEqual(1, tree.RootNodes.Count);

			// Test Root
			var root = tree.RootNodes[0];
			Assert.AreEqual("Portable Executable File (32bit version)", root.Value.Text);
			Assert.AreEqual("PE_FILE", root.Value.Path);
			Assert.AreEqual(null, root.Value.Comment);
			Assert.AreEqual(0, root.Value.Offset);
			Assert.AreEqual(752, root.Value.Size);

			// 5 children of root
			// (DOS, COFF, 3 IMAGE_SECTION_HEADERs )
			Assert.AreEqual(5, root.ChildNodes.Count);

			// Test 'PE_FILE\IMAGE_NT_HEADER\IMAGE_FILE_HEADER'
			var imageFileHeader = root.ChildNodes[1].ChildNodes[1];
			Assert.AreEqual("IMAGE_FILE_HEADER", imageFileHeader.Value.Text);
			Assert.AreEqual(@"PE_FILE\IMAGE_NT_HEADER\IMAGE_FILE_HEADER", imageFileHeader.Value.Path);
			Assert.AreEqual(null, imageFileHeader.Value.Comment);
			Assert.AreEqual(228, imageFileHeader.Value.Offset);
			Assert.AreEqual(20, imageFileHeader.Value.Size);

			// Test 'PE_FILE\IMAGE_NT_HEADER\IMAGE_FILE_HEADER\NumberOfSymbols'
			var numberOfSymbols = root.ChildNodes[1].ChildNodes[1].ChildNodes[4];
			Assert.AreEqual("NumberOfSymbols", numberOfSymbols.Value.Text);
			Assert.AreEqual(@"PE_FILE\IMAGE_NT_HEADER\IMAGE_FILE_HEADER\NumberOfSymbols", numberOfSymbols.Value.Path);
			Assert.AreEqual("NumberOfSymbols", numberOfSymbols.Value.Comment);
			Assert.AreEqual(240, numberOfSymbols.Value.Offset);
			Assert.AreEqual(4, numberOfSymbols.Value.Size);

			// Test 'PE_FILE\IMAGE_SECTION_HEADER(2)\PhysicalAddress'
			var physicalAddress = root.ChildNodes[4].ChildNodes[1];
			Assert.AreEqual("PhysicalAddress", physicalAddress.Value.Text);
			Assert.AreEqual(@"PE_FILE\IMAGE_SECTION_HEADER(2)\PhysicalAddress", physicalAddress.Value.Path);
			Assert.AreEqual("PhysicalAddress", physicalAddress.Value.Comment);
			Assert.AreEqual(720, physicalAddress.Value.Offset);
			Assert.AreEqual(4, physicalAddress.Value.Size);
		}

		[Test]
		public void testFindPath()
		{
			var fileContents = new FileContents(@"..\..\TestResource\notepad.exe");
			var fileFormat = new FileFormat(@"..\..\TestResource\Windows PE Format.xml", fileContents);

			var formatNode = fileFormat.FindPath(@"PE_FILE\IMAGE_SECTION_HEADER(2)\PhysicalAddress");
			Assert.AreEqual(@"PE_FILE\IMAGE_SECTION_HEADER(2)\PhysicalAddress", formatNode.Value.Path);
		}

		[Test]
		public void testFindOffset()
		{
			var fileContents = new FileContents(@"..\..\TestResource\notepad.exe");
			var fileFormat = new FileFormat(@"..\..\TestResource\Windows PE Format.xml", fileContents);

			var formatNode = fileFormat.FindOffset( 721 );
			Assert.AreEqual(@"PE_FILE\IMAGE_SECTION_HEADER(2)\PhysicalAddress", formatNode.Value.Path);
		}

	}
}
